#include <windows.h>
#include <tchar.h>
#include "canvas.h"
#include <windowsx.h>
#include "gobang_ui.h"
#include <stdio.h>
#include "winapi_adaptor.h"

static gobang_ui* gobang_;
static HINSTANCE hinstance_;
static canvas_t canvas_;

VOID FullScreen(HWND hwnd, BOOL full){
    static RECT pos;
    static LONG style;
    static LONG styleex;
    if(full){
        HMONITOR hMon = MonitorFromWindow(hwnd, MONITOR_DEFAULTTONEAREST);
        MONITORINFO oMonitor;        
        oMonitor.cbSize = sizeof(oMonitor);
        if(!GetMonitorInfo(hMon, &oMonitor))return;

        RECT rc = oMonitor.rcMonitor;    
        style = GetWindowLong(hwnd, GWL_STYLE);
        styleex = GetWindowLong(hwnd, GWL_EXSTYLE);
        GetWindowRect(hwnd, &pos);
        SetWindowLong(hwnd, GWL_STYLE, WS_POPUP);
        SetWindowLong(hwnd, GWL_EXSTYLE, 0);
        SetWindowPos(hwnd, HWND_TOPMOST, 0, 0, rc.right - rc.left, rc.bottom - rc.top, SWP_SHOWWINDOW);        
    } else {
        SetWindowLong(hwnd, GWL_STYLE, style);
        SetWindowLong(hwnd, GWL_EXSTYLE, styleex);        
        SetWindowPos(hwnd, HWND_NOTOPMOST, pos.left, pos.top, pos.right - pos.left, pos.bottom - pos.top, SWP_SHOWWINDOW);        
    }    
}

//绘制窗口
VOID MainWndOnPaint(HWND hwnd){    
    PAINTSTRUCT ps;
    BeginPaint(hwnd, &ps);
    if(!canvas_){
        canvas_ = canvas_create(hwnd);
        if(!canvas_){
            MessageBox(hwnd, TEXT("Create D2D1 Render Error"), NULL, MB_OK);
            PostQuitMessage(1);
            return ;
        }
    } 
    canvas_begin_draw(canvas_);
    gobang_ui_update(gobang_, canvas_);
    canvas_end_draw(canvas_);
    EndPaint(hwnd, &ps);    
}

void MainWndOnSize(HWND hwnd){
    RECT rc;
    GetClientRect(hwnd, &rc);
    gobang_ui_resize(gobang_, rc.right, rc.bottom);
    if(canvas_)canvas_resize(canvas_,rc.right, rc.bottom);
}

void MainWndOnCreate(HWND hwnd){
    RECT rc;
    GetClientRect(hwnd, &rc);
    gobang_ = gobang_ui_init(rc.right, rc.bottom);    
}

BOOL OnKey(HWND hwnd, UINT code){
    switch (code){
    case VK_ESCAPE:
        PostQuitMessage(0);
        return TRUE;
    default:
        break;
    }  
    return FALSE;  
}

void OnMouse(HWND hwnd, UINT message, LPARAM lParam){
    int state;
    switch (message){  
        case WM_MOUSEMOVE:
            gobang_ui_mouse_move(gobang_, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));                   
            break;    
        case WM_LBUTTONDOWN:  
            SetCapture(hwnd);
            gobang_ui_mouse_down(gobang_, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
            break;
        case WM_LBUTTONUP:
            ReleaseCapture();
            gobang_ui_mouse_up(gobang_, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
            break;
        default:
            return;
    }
    state = gobang_ui_state(gobang_);
    if(state == GOBANG_UI_NEED_UPDATE){
        InvalidateRect(hwnd, NULL, FALSE);
    }else if(state == GOBANG_UI_NEED_QUIT){
        PostQuitMessage(0);
    }
}

//主窗口过程
LRESULT CALLBACK MainWndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam){
    switch (message){  
        case WM_MOUSEMOVE:  
        case WM_LBUTTONDOWN: 
        case WM_LBUTTONUP:
            OnMouse(hwnd, message, lParam);
            break;    
        case WM_KEYDOWN:    
            OnKey(hwnd, wParam);
            break;          
        case WM_CREATE:
            MainWndOnCreate(hwnd);
            break;               
        case WM_DESTROY:
            PostQuitMessage(0);
            break;
        case WM_PAINT:
            MainWndOnPaint(hwnd);
            break; 
        case WM_SIZE:
            MainWndOnSize(hwnd);
            break;  

        default:
            return DefWindowProc(hwnd, message, wParam, lParam);
    }
    return 1;
}

//注册主窗口类
BOOL RegisterWindowClass(){
    WNDCLASS wc = {0};
    wc.style = CS_VREDRAW|CS_HREDRAW;    
    wc.hIcon = LoadIcon(hinstance_, MAKEINTRESOURCE(1));
    wc.hCursor = LoadCursor(NULL, IDC_ARROW);
    wc.lpfnWndProc = MainWndProc;
    wc.hInstance = hinstance_;     
    wc.lpszClassName = TEXT("MainWindowClass");
    return RegisterClass(&wc);
}

//入口函数
int WINAPI _tWinMain(HINSTANCE hInst,HINSTANCE hPrev,LPTSTR lpCmdLine,int nCmdShow){
	hinstance_ = hInst;
    InitWinAPI();
    gobang_ = gobang_ui_init(600,400);
	RegisterWindowClass();	
	HWND hwnd = CreateWindow(TEXT("MainWindowClass"),TEXT("五子棋"),
        //(WS_OVERLAPPED|WS_CAPTION|WS_MINIMIZEBOX|WS_SYSMENU), //固定窗口大小
        WS_OVERLAPPEDWINDOW,  //可变窗口大小
        CW_USEDEFAULT,CW_USEDEFAULT,400,300,NULL,NULL,hinstance_,NULL);	
#ifdef NDEBUG
    FullScreen(hwnd, TRUE);
#endif
	ShowWindow(hwnd, nCmdShow);
    MSG msg;
    while(GetMessage(&msg, NULL, 0, 0)){
        TranslateMessage(&msg);
        DispatchMessage(&msg);
    }
    return msg.wParam;
}
